package dao

import (
	__ "activity_srv/basic/proto"
	"activity_srv/handler/models"
	"errors"
	"fmt"
	"github.com/skip2/go-qrcode"
	"image"
	"image/draw"
	"image/jpeg"
	"io"
	"net/http"
	"net/url"
	"os"
	"path/filepath"
	"strconv"
	"strings"
)

// ShowDistributionPoster 二级分销海报展示
func ShowDistributionPoster(in *__.DistributionPosterShowReq) (string, error) {
	var distribution models.DistributionData
	var err error
	distribution.Id = uint32(in.Id)
	if err = distribution.GetDistributionId(); err != nil {
		return "", errors.New("查询失败")
	}
	if err = distribution.GetPoster(); err != nil {
		return "", errors.New("查询失败")
	}

	resp, err := http.Get(distribution.Poster)
	if err != nil || resp.StatusCode != 200 {
		fmt.Printf("下载失败: %s，错误: %v\n", distribution.Poster, err)
		return "", err
	}
	defer resp.Body.Close()
	// 1. 从 UL 中提取文件名（关键：解决路径非法问题）
	filename := getFilenameFromURL(distribution.Poster)
	if filename == "" {
		return "", errors.New("无法提取文件名")
	}
	// 2. 规范路径拼接（用 filepath.Join 处理系统路径）
	saveDir := "../../static/upload"
	savePath := filepath.Join(saveDir, filename)
	// 3. 创建文件并处理错误（不要忽略 err！）
	file, err := os.Create(savePath)
	if err != nil {
		fmt.Printf("创建文件失败: %v，路径: %s\n", err, savePath)
		return "", err
	}
	defer file.Close()
	// 4. 写入文件内容并处理错误
	_, err = io.Copy(file, resp.Body)
	if err != nil {
		fmt.Printf("写入文件失败: %v，路径: %s\n", err, savePath)
		return "", err
	}

	fmt.Printf("已保存: %s 到 %s\n", filename, savePath)
	return distribution.Poster, nil
}

// getFilenameFromURL 从 URL 中提取纯净的文件名
func getFilenameFromURL(urlImg string) string {
	// 解析 URL
	u, err := url.Parse(urlImg)
	if err != nil {
		// 解析失败时，截取 URL 最后一段
		parts := strings.Split(urlImg, "/")
		return parts[len(parts)-1]
	}
	// 从路径中提取最后一段作为文件名
	pathParts := strings.Split(u.Path, "/")
	return pathParts[len(pathParts)-1]
}

// 获取用户Id
func GetUserId(in *__.AddUserDistributionPosterQuCodeReq) uint32 {
	var user models.User
	var err error
	user.Id = uint32(in.UserId)
	if err = user.GetUserIdDistribution(); err != nil {
		fmt.Println("用户Id不存在")
		return 0
	}
	return user.Id
}

// GenerateQrCode 二维码生成
func GenerateQrCode(in *__.AddUserDistributionPosterQuCodeReq) string {
	user := GetUserId(in)
	userId := strconv.Itoa(int(user))
	//要生成二维码的内容
	content := "https://example.com/invite?code=ABC123"
	//生成二维码并保存图片
	filename := "../../static/upload/qrcodeDistribution" + userId + ".png"
	err := qrcode.WriteFile(content, qrcode.Medium, 200, filename)
	if err != nil {
		fmt.Printf("生成二维码失败: %v\n", err)
	}
	fmt.Println("生成图片成功")

	return "qrcodeDistribution" + userId + ".png"
}

// PosterGeneration 海报加二维码生成
func PosterGeneration(in *__.AddUserDistributionPosterQuCodeReq) string {
	userId := GetUserId(in)
	filename := GenerateQrCode(in)
	// 打开第一张图片（背景图片）
	bgFile, err := os.Open("../../static/upload/QQ20250826-175443.jpg")
	if err != nil {
		panic(err)
	}
	defer bgFile.Close()
	// 打开第二张图片（要嵌套的图片）
	fgFile, err := os.Open("../../static/upload/" + filename)
	if err != nil {
		panic(err)
	}
	defer fgFile.Close()
	// 解码图片
	bgImg, _, err := image.Decode(bgFile)
	if err != nil {
		panic(err)
	}
	fgImg, _, err := image.Decode(fgFile)
	if err != nil {
		panic(err)
	}
	// 创建新的画布，大小与背景图片相同
	result := image.NewRGBA(bgImg.Bounds())
	// 首先绘制背景图片
	draw.Draw(result, bgImg.Bounds(), bgImg, image.Point{}, draw.Src)
	// 计算嵌套位置（第一张图片下边的最中间）
	bgBounds := bgImg.Bounds()
	fgBounds := fgImg.Bounds()
	// 计算x坐标：背景宽度的一半减去前景宽度的一半
	x := (bgBounds.Dx() - fgBounds.Dx()) / 2
	// y坐标：背景高度减去前景高度（放在底部）
	y := bgBounds.Dy() - fgBounds.Dy() + 20
	if x < 0 {
		x = 0
	}
	if y < 0 {
		y = 0
	}
	placementRect := image.Rect(x, y, x+fgBounds.Dx(), y+fgBounds.Dy())
	draw.Draw(result, placementRect, fgImg, image.Point{}, draw.Over)
	filenameUrl := "result" + strconv.Itoa(int(userId)) + ".jpg"
	outFile, err := os.Create("../../static/upload/" + filenameUrl)
	if err != nil {
		panic(err)
	}
	defer outFile.Close()
	err = jpeg.Encode(outFile, result, &jpeg.Options{Quality: 90})
	if err != nil {
		panic(err)
	}
	fmt.Println("图片名称为", filenameUrl)

	return filenameUrl
}

func AddUserDistributionPosterQrCode(in *__.AddUserDistributionPosterQuCodeReq) (models.DistributionQrCode, error) {
	filename := PosterGeneration(in)
	var posterQrCode models.DistributionQrCode
	var err error
	userId := GetUserId(in)
	posterQrCode.UserId = userId
	if err = posterQrCode.DetailUserDistributionQrCode(); err != nil {
		fmt.Println("当前用户已存在")
		return posterQrCode, nil
	}
	if posterQrCode.Id != 0 {
		fmt.Println("当前用户已存在")
		return posterQrCode, nil
	}
	posterQrCode.PosterQrCode = filename
	posterQrCode.PosterUrl = "http://127.0.0.1:8080/upload/" + posterQrCode.PosterQrCode
	if err = posterQrCode.AddDistributionQrCode(); err != nil {
		return posterQrCode, nil
	}
	return posterQrCode, nil
}
